#include "indexvariable.h"

IndexVariable::IndexVariable(Variable *sig, vector<Expr *> index,int fila,int col):Variable(sig,fila,col)
{
    this->index=index;
}

void IndexVariable::setindex(vector<Expr *> index)
{
    this->index = index;
}

vector<Expr *> IndexVariable::getindex()
{
    return this->index;
}

string IndexVariable::is()
{
    return "Literal_Identificador_index";
}

Tipo_ts *IndexVariable::validarSemantica(Tabla_Simbolos *tabla_de_tipo, Tabla_Simbolos *tabla_de_varaible)
{
    Item_ts *its = tabla_de_varaible->get(this->getValor());
            if(its!=0){
                if(its->getTipo()->is().compare("ARREGLO")== 0 ){
                    for(int i=0;i<(int)this->getindex().size();i++){
                        Tipo_ts *tts = this->getindex().at(i)->validarSemantica(tabla_de_tipo,tabla_de_varaible);
                        if(tts->is()!="ENTERO"){
                            stringstream out;
                            out<<"Parametros no son de tipo entero// Fila: "<<this->getFila()<<endl;
                            throw exception(out.str().c_str());
                        }

                    }
                    Arreglo *arr = (Arreglo*)its->getTipo();
                        if(arr->getDims().size()!=this->getindex().size()){
                            stringstream out;
                            out<<"Cantidad de parametros es incorrecta// Fila: "<<this->getFila()<<endl;
                            throw exception(out.str().c_str());
                        }
                        //versi es registro
                        if(arr->getTipo()->is().compare("REGISTRO")==0&&this->getsig()!=0){
                            Registro *r = (Registro *)arr->getTipo();
                            return this->getsig()->validarSemantica(tabla_de_tipo,r->getTs());
                        }else{
                            return arr->getTipo();
                        }
                }else{
                    stringstream out;
                    out<<"Se esperaba un arreglo// Fila: "<<this->getFila()<<endl;
                    throw exception(out.str().c_str());
                }
            }else{
                stringstream out;
                out<<"Variable No exite "<<this->getValor()<<"// Fila: "<<this->getFila()<<endl;
                throw exception(out.str().c_str());
            }
}

Codigo_Lugar IndexVariable::generarCodigo(GenerarVariable *var, Tabla_Simbolos *tabla_de_tipo, Tabla_Simbolos *tabla_de_varaible)
{
    string codigo = "_"+this->getValor()+"_";
    for (int i =0; i<this->index.size();i++){
        codigo += "["+this->index.at(i)->generarCodigo(var,tabla_de_tipo,tabla_de_varaible).codigo+"]";
    }
    Codigo_Lugar cl;
    cl.codigo = codigo;
    return cl;

}
